﻿using System;
using System.Configuration;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Net.Http.Headers;
using System.Web;
using System.Web.Http;
using Common.Logging;
using Newtonsoft.Json;
using OutDbContext;
using Senparc.Weixin;
using Senparc.Weixin.Exceptions;
using Senparc.Weixin.MP;
using Senparc.Weixin.MP.AdvancedAPIs;
using Senparc.Weixin.MP.AdvancedAPIs.OAuth;
using User.Api.Helpers;
using User.Api.Dto.Auth;

namespace User.Api.Controllers
{
    public class AuthController : ApiController
    {
        private static readonly ILog Logger = LogManager.GetLogger(typeof(AuthController));
        private static readonly string WxOauth2State = "GbkYin666";

        [AllowAnonymous]
        [HttpGet]
        [ActionName("WxOauth2")]
        public HttpResponseMessage WxOauth2(string url, string code, string state)
        {
            string failedUrl = ConfigurationManager.AppSettings["H5BaseAddress"] + "/index/401";

            var appId = ConfigurationManager.AppSettings["WeixinAppId"];
            var secret = ConfigurationManager.AppSettings["WeixinAppSecret"];

            if (string.IsNullOrEmpty(code))
            {
                var res = Request.CreateResponse(HttpStatusCode.Redirect);
                res.Headers.Location = new Uri(failedUrl);
                return res;
            }

            if (state != WxOauth2State)
            {
                var res = Request.CreateResponse(HttpStatusCode.Redirect);
                res.Headers.Location = new Uri(failedUrl);
                return res;
            }

            OAuthAccessTokenResult result = null;

            //通过，用code换取access_token
            try
            {
                result = OAuthApi.GetAccessToken(appId, secret, code);
            }
            catch (Exception ex)
            {
                Logger.ErrorFormat("微信网页授权获取用户信息第一步出错，授权码:{0},信息：{1}", code, JsonConvert.SerializeObject(ex));

                var res = Request.CreateResponse(HttpStatusCode.Redirect);
                res.Headers.Location = new Uri(failedUrl);
                return res;
            }
            if (result.errcode != ReturnCode.请求成功)
            {
                var res = Request.CreateResponse(HttpStatusCode.Redirect);
                res.Headers.Location = new Uri(failedUrl);
                return res;
            }

            //OAuthUserInfo userInfo = null;
            //try
            //{
            //    userInfo = OAuthApi.GetUserInfo(result.access_token, result.openid);
            //    // TODO 获取用户信息
            //}
            //catch (ErrorJsonResultException ex)
            //{
            //    Logger.ErrorFormat("微信网页授权获取用户信息第二步出错，信息：{0}", JsonConvert.SerializeObject(ex));
            //}

            long userId = 0;
            var openId = result.openid;

            using (var ctx = new HzfyWeiXinEntities())
            {
                var user = ctx.WxUser.FirstOrDefault(x => x.OpenId == openId);
                if (user != null)
                {
                    user.RecStatus = 1;
                    user.LastActiveDt = DateTime.Now;
                    user.UnsubscribeDt = null;
                    user.RecUpdateDt = DateTime.Now;
                }
                else
                {
                    user = new OutDbContext.WxUser
                    {
                        OpenId = openId,
                        SubscribeDt = DateTime.Now,
                        LastActiveDt = DateTime.Now,
                        //IsBitcareMember = false,
                        RecStatus = 1,
                        RecCreateDt = DateTime.Now
                    };

                    ctx.WxUser.Add(user);
                }

                ctx.SaveChanges();
                userId = user.Id;
            }

            var response = Request.CreateResponse(HttpStatusCode.Redirect);
            response.Headers.Location = new Uri(url);

            var cookie = new CookieHeaderValue("AzuCookie",
                LocalUserTokenHelper.GenerateLocalToken(userId, openId));
            //cookie.Domain = Request.RequestUri.Host;
            cookie.Path = "/";
            response.Headers.AddCookies(new[] { cookie });

            return response;
        }

        [HttpGet]
        [AllowAnonymous]
        [ActionName("GetWxOauth2Url")]
        public string GetWxOauth2Url(string url)
        {
            var baseAddress = ConfigurationManager.AppSettings["BaseAddress"];
            var appId = ConfigurationManager.AppSettings["WeixinAppId"];

            var oauth2Url = OAuthApi.GetAuthorizeUrl(appId,
                baseAddress
                + "api/Auth/WxOauth2?url="
                + HttpUtility.UrlEncode(url), WxOauth2State, OAuthScope.snsapi_userinfo);

            return oauth2Url;
        }

        /// <summary>
        /// 获取oauth2的网页地址
        /// </summary>
        /// <param name="routePath">比如 "/index/portal/"</param>
        /// <returns></returns>
        [HttpGet]
        [AllowAnonymous]
        [ActionName("GetH5Url")]
        public string GetH5Url(string routePath)
        {
            var h5BaseAddress = ConfigurationManager.AppSettings["H5BaseAddress"];
            var baseAddress = ConfigurationManager.AppSettings["BaseAddress"];
            var appId = ConfigurationManager.AppSettings["WeixinAppId"];

            var url = h5BaseAddress + routePath;

            var oauth2Url = OAuthApi.GetAuthorizeUrl(appId,
                baseAddress
                + "api/Auth/WxOauth2?url="
                + HttpUtility.UrlEncode(url), WxOauth2State, OAuthScope.snsapi_userinfo);

            return oauth2Url;
        }
      
        /// <summary>
        ///  判断openid是否关注公众号
        /// </summary>
        /// <returns>0-关注，1-没关注</returns>
        [HttpGet]
        [ActionName("CheckSubscribe")]
        public CheckSubscribeResponse CheckSubscribe(string openId)
        {
            if (string.IsNullOrEmpty(openId))
            {
                var azUser = AzUser.GetInApi(Request);
                openId = azUser.OpenId;
            }
            try
            {
                var appId = ConfigurationManager.AppSettings["WeixinAppId"];
                var openinfo = UserApi.Info(appId, openId);
                return new CheckSubscribeResponse()
                {
                    ResultCode = openinfo.subscribe == 0 ? "1" : "0",
                    ResultMsg = "",
                };
            }
            catch (Exception ex)
            {
            }
            return new CheckSubscribeResponse()
            {
                ResultCode = "1",
                ResultMsg = "",
            };
        }
    }
}
